home *** CD-ROM | disk | FTP | other *** search
/ Night Owl 6 / Night Owl's Shareware - PDSI-006 - Night Owl Corp (1990).iso / 007a / cug315.zip / DOS_FUNC.C < prev    next >
C/C++ Source or Header  |  1990-05-16  |  13KB  |  447 lines

  1.  
  2. /* count_files() added 11/89 by T Clune for R Webb.  count_files() */
  3. /* accepts a filespec template and returns the number of matching files */
  4.  
  5. /* fget_time_date() added 10/89 by T Clune, to construct a string */
  6. /* that identifies a file's time and date of creation.  Added by */
  7. /* T Clune for F Van de Velde */
  8.  
  9. /* get_dir() modified to accept pointers instead of character arrays */
  10. /* for the returned names.  Now get_dir() is compatible with menu() in */
  11. /* menu.c, and dir_menu() in that file has been eliminated.  Changed */
  12. /* 12/88 by T Clune */
  13.  
  14. /* del_fines() and parse_filename() deleted 12/88 by T Clune.  Use */
  15. /* del_fhandle() for all file deletions */
  16.  
  17. /* dos_func.c was created 11/88 by T Clune to incorporate the various */
  18. /* DOS software interrupt functions that were spread over a variety of */
  19. /* applications into one file.  Copyright (c) 1988, Eye Research Institute */
  20. /* All Rights Reserved. */
  21.  
  22.  
  23. #include "dos_func.h" /* this file's typedefs and declarations */
  24.  
  25. #include <stdio.h>
  26. #include <string.h>
  27. #include <dos.h>
  28. #include <malloc.h>
  29.  
  30.     /* support functions for del_fhandle() and get_dir() */
  31. static unsigned int get_first_filename();
  32. static unsigned int get_next_filename();
  33. static unsigned long get_dta();
  34. static void set_dta();
  35.  
  36.  
  37.  
  38.  
  39. /* count_files() looks in the directory in filespec for the file(s) specified */
  40. /* by filespec (same format as DOS dir command for filespec).  The function */
  41. /* returns the number of matching files found.  */
  42. /* added 11/89 by T Clune */
  43.  
  44. int count_files(filespec)
  45. char filespec[];
  46. {
  47.     int i=0;    /* the number of matching files counter */
  48.     unsigned int cflag; /* the carry flag returned by get_first_filename() */
  49.             /* and get_next_filename() function calls */
  50.     unsigned long int fnameptr;  /* flespec cast as an unsigned long int */
  51.     dta dir_struct;  /* the file dta */
  52.     unsigned long psp_dta;  /* the dta pointer on entry to get_dir() */
  53.  
  54.  
  55.     psp_dta=get_dta();
  56.     set_dta((unsigned long)&dir_struct);
  57.  
  58.     /* get first filename */
  59.     fnameptr=(unsigned long int)filespec;
  60.     cflag=get_first_filename(fnameptr);
  61.  
  62.     while(!cflag)
  63.     {
  64.     cflag=get_next_filename(fnameptr);
  65.     i++;    /* increment match-count */
  66.     }
  67.  
  68.     /* restore original dta before exiting */
  69.     set_dta(psp_dta);
  70.  
  71.     return i;  /* return number of matches found */
  72.  
  73. }
  74.  
  75.  
  76.  
  77.  
  78.  
  79.  
  80. /* del_fhandle() was modified 12/88 by T. Clune to support wildcards. */
  81. /* del_fhandle() deletes all files specified by FILESPEC.  The advantage */
  82. /* of del_fhandle() over del_files() is that you can specify a path instead */
  83. /* of having to use the default path. Returns 0 if successful, 1 if not. */
  84. /* See Programmers Problem Solver, p. 272-275 for details of function 0x41. */
  85.  
  86. int del_fhandle(filespec)
  87. char filespec[];
  88. {
  89.      /* the first block of declarations is for getting the filenames */
  90.     dta dir_struct;  /* the file dta */
  91.     unsigned long psp_dta;  /* the dta pointer on entry to get_dir() */
  92.     unsigned long int fnameptr; /* filespec cast as a number */
  93.     unsigned int cflag; /* the carry flag returned by get_first_filename() */
  94.         /* and get_next_filename() */
  95.     char *ptr;
  96.     char pathname[40];
  97.     char fullname[80];
  98.  
  99.     /* this block of declarations is for doing the deletions */
  100.     address_union address;
  101.     union REGS inregs, outregs;
  102.     struct SREGS segregs;
  103.  
  104.     /* get path name of filespec */
  105.     strcpy(pathname, filespec);
  106.     ptr=strrchr(pathname, '\\');
  107.     if(!ptr)
  108.     ptr=strrchr(pathname,':');
  109.     if(ptr)
  110.     {
  111.     ptr++;
  112.     *ptr ='\0';
  113.     }
  114.     else
  115.     pathname[0]='\0';
  116.  
  117.     psp_dta=get_dta();
  118.     set_dta((unsigned long)&dir_struct);
  119.  
  120.     /* get first filename */
  121.     fnameptr=(unsigned long int)filespec;
  122.     cflag=get_first_filename(fnameptr);
  123.  
  124.     /* set up the delete-file software interrupt */
  125.     address.pointer=(unsigned long int)fullname;
  126.     segregs.ds=address.s.segment;
  127.     inregs.x.dx=address.s.offset;
  128.     inregs.h.ah=0x41;   /* the erase filespec function in DOS */
  129.  
  130.     while(!cflag)
  131.     {
  132.         /* construct name of matching file (including path) to delete */
  133.     strcpy(fullname, pathname);
  134.     strcat(fullname, dir_struct.name);
  135.     intdosx(&inregs, &outregs, &segregs);  /* delete the file */
  136.     if(outregs.x.cflag) /* abort on failure to delete */
  137.         break;
  138.     cflag=get_next_filename(fnameptr);
  139.     }
  140.  
  141.     /* restore original dta before exiting */
  142.     set_dta(psp_dta);
  143.  
  144.     return outregs.x.cflag;
  145.  
  146. }
  147.  
  148.  
  149.  
  150.  
  151.  
  152.  
  153. /* disk_space() returns the number of bytes available on a disk */
  154. /* you specify the disk in the call (0 = default drive, 1=A, etc.) */
  155. /* and it returns a LONG INT with the size of the available space */
  156. /* any DOS programming guide will explain the routine, but two that */
  157. /* did a good job are _Programmer's Guide to MS DOS_ by Dennis Jump */
  158. /* p. 95-96 and my old stand-by _Programmer's Problem Solver_ by Robert */
  159. /* Jourdain, p.247. */
  160.  
  161. long disk_space(drive)
  162. int drive;  /* drive choice. 0=default, 1=A, 2=B, etc. */
  163. {
  164.     long bytes_free;    /* return value in bytes for disk specified */
  165.     union REGS inregs, outregs;     /* as per dos.h */
  166.  
  167.     inregs.h.ah = 0x36;    /* function call specifies get disk space */
  168.     inregs.h.dl = drive;   /* which drive? */
  169.  
  170.     intdos(&inregs, &outregs); /* call the interrupt */
  171.  
  172.             /* calculate bytes free */
  173.     bytes_free = (long) outregs.x.ax*outregs.x.bx*outregs.x.cx;
  174.  
  175.     return bytes_free;
  176.  
  177. }
  178.  
  179.  
  180.  
  181.  
  182. /* fget_time_date() gets the time and date of creation of the file FILESPEC */
  183. /* and writes the data as a string into TIMEDATE, in the format; */
  184. /* MM-DD-YY HH:MM.SS  where MM is month, DD is day, YY is year, HH is HOUR, and */
  185. /* MM is minutes, and SS is seconds.  The TIMEDATE string length is */
  186. /* <= 18 chars, including terminating null. Added 10/89 by T Clune. */
  187.  
  188. void fget_time_date(filespec,timedate)
  189. char filespec[], timedate[];
  190. {
  191.     dta dir_struct;  /* the file dta */
  192.     address_union address;
  193.     unsigned long psp_dta; /* the dta on entry to fname_unused() */
  194.     union REGS regs;
  195.     struct SREGS segregs;
  196.     filestamp td;
  197.     int i;
  198.     char string[10];
  199.  
  200.     if(fname_unused(filespec))
  201.     {
  202.     strcpy(timedate, "00-00-00 0:00.00");
  203.     return;
  204.     }
  205.  
  206.     psp_dta=get_dta();
  207.     set_dta((unsigned long)&dir_struct);
  208.  
  209.     /* get first filename */
  210.     address.pointer=(unsigned long int)&filespec[0];
  211.     segregs.ds=address.s.segment;
  212.     regs.x.dx=address.s.offset;
  213.     regs.x.cx=0;  /* no funny attributes in file */
  214.     regs.h.ah=0x4E;   /* first file match function number of int 0x21 */
  215.     intdosx(®s, ®s, &segregs);
  216.     /* the 0x21 function 0x57 is the "official" time/date interrupt */
  217.     /* function, but anything that gets a file using the file handle */
  218.     /* method will initialize the dta for you. */
  219.  
  220.     /* restore original dta before exiting */
  221.     set_dta(psp_dta);
  222.     td.w.time=dir_struct.time;
  223.     td.w.date=dir_struct.date;
  224.     i=td.b.mon;
  225.     itoa(i,string,10);
  226.     strcpy(timedate, string);
  227.     strcat(timedate,"-");
  228.     i=td.b.day;
  229.     itoa(i,string,10);
  230.     strcat(timedate, string);
  231.     strcat(timedate,"-");
  232.     i=td.b.yr;
  233.     i +=80;
  234.     itoa(i,string,10);
  235.     strcat(timedate, string);
  236.     strcat(timedate," ");
  237.     i=td.b.hrs;
  238.     itoa(i,string,10);
  239.     strcat(timedate, string);
  240.     strcat(timedate,":");
  241.     i=td.b.mins;
  242.     if(i<10)
  243.     strcat(timedate,"0");
  244.     itoa(i,string,10);
  245.     strcat(timedate, string);
  246.     strcat(timedate,".");
  247.     i=td.b.secs;
  248.     if(i<10)
  249.     strcat(timedate,"0");
  250.     itoa(i,string,10);
  251.     strcat(timedate, string);
  252.  
  253. }
  254.  
  255.  
  256.  
  257.  
  258.  
  259.  
  260. /* fname_unused() checks the directory in filespec for the file(s) specified */
  261. /* by filespec to see whether the name has been used already.   Returns 0 if */
  262. /* name is already used, 1 otherwise */
  263.  
  264. int fname_unused(filespec)
  265. char filespec[];
  266. {
  267.     dta dir_struct;  /* the file dta */
  268.     address_union address;
  269.     unsigned long psp_dta; /* the dta on entry to fname_unused() */
  270.     union REGS inregs, outregs;
  271.     struct SREGS segregs;
  272.  
  273.     psp_dta=get_dta();
  274.     set_dta((unsigned long)&dir_struct);
  275.  
  276.     /* get first filename */
  277.     address.pointer=(unsigned long int)&filespec[0];
  278.     segregs.ds=address.s.segment;
  279.     inregs.x.dx=address.s.offset;
  280.     inregs.x.cx=0;  /* no funny attributes in file */
  281.     inregs.h.ah=0x4E;   /* first file match function number of int 0x21 */
  282.     intdosx(&inregs, &outregs, &segregs);
  283.  
  284.     /* restore original dta before exiting */
  285.     set_dta(psp_dta);
  286.  
  287.     return outregs.x.cflag;
  288.  
  289. }
  290.  
  291.  
  292.  
  293.  
  294.  
  295.  
  296. /* get_dir() looks in the directory in filespec for the file(s) specified */
  297. /* by filespec (same format as DOS dir command for filespec)  The matching */
  298. /* files are written into fnames.  The function returns the number of */
  299. /* matching files found, or MAX_FILES+1 if too many matches for the array  */
  300.  
  301. int get_dir(filespec,fnames,max_files)
  302. char filespec[], *fnames[];
  303. int max_files;  /* the size of fnames array */
  304. {
  305.     int i=0;    /* the number of matching files counter */
  306.     int name_size;  /* strlen(filename) */
  307.     unsigned int cflag; /* the carry flag returned by get_first_filename() */
  308.             /* and get_next_filename() function calls */
  309.     unsigned long int fnameptr;  /* flespec cast as an unsigned long int */
  310.     dta dir_struct;  /* the file dta */
  311.     unsigned long psp_dta;  /* the dta pointer on entry to get_dir() */
  312.  
  313.  
  314.     psp_dta=get_dta();
  315.     set_dta((unsigned long)&dir_struct);
  316.  
  317.     /* get first filename */
  318.     fnameptr=(unsigned long int)filespec;
  319.     cflag=get_first_filename(fnameptr);
  320.  
  321.     while((!cflag) && i<max_files)
  322.     {
  323.     name_size=strlen(dir_struct.name);
  324.     fnames[i]=malloc(name_size+1);
  325.     if(fnames[i]==NULL)
  326.     {
  327.         printf("Error allocating file names buffer space.  Program aborting.\n");
  328.         exit(-1);
  329.     }
  330.     strcpy(fnames[i], dir_struct.name); /* write matching filename into */
  331.                     /* the fnames array */
  332.     cflag=get_next_filename(fnameptr);
  333.     i++;    /* increment match-count */
  334.     }
  335.     if((i == max_files) && (!cflag))
  336.     i++;
  337.  
  338.     /* restore original dta before exiting */
  339.     set_dta(psp_dta);
  340.  
  341.     return i;  /* return number of matches found */
  342.  
  343. }
  344.  
  345.  
  346.  
  347.  
  348.  
  349.  
  350. /* get_dta() returns the address of the current dta, as an unsigned long int */
  351.  
  352. static unsigned long get_dta()
  353. {
  354.     address_union address;
  355.     union REGS inregs, outregs;
  356.     struct SREGS segregs;
  357.  
  358.     inregs.h.ah=0x2f;
  359.     intdosx(&inregs, &outregs, &segregs);
  360.  
  361.     address.s.segment=segregs.es;
  362.     address.s.offset=outregs.x.bx;
  363.  
  364.     return address.pointer;
  365.  
  366. }
  367.  
  368.  
  369.  
  370.  
  371.  
  372.  
  373.  
  374.  
  375. /* get_first_filename() gets the first match of the filespec and returns 0 */
  376. /* if a match was found, non-zero otherwise.  The name is in the current dta */
  377.  
  378. static unsigned int get_first_filename(fnameptr)
  379. unsigned long int fnameptr;
  380. {
  381.     address_union address;  /* address conversion union */
  382.     union REGS inregs, outregs;
  383.     struct SREGS segregs;
  384.  
  385.  
  386.     /* get first filename */
  387.     address.pointer=fnameptr;
  388.     segregs.ds=address.s.segment;
  389.     inregs.x.dx=address.s.offset;
  390.     inregs.x.cx=0;  /* no funny attributes in file */
  391.     inregs.h.ah=0x4E;   /* first file match function number of int 0x21 */
  392.     intdosx(&inregs, &outregs, &segregs);
  393.  
  394.     return outregs.x.cflag;
  395.  
  396. }
  397.  
  398.  
  399. /* get_next_filename() gets a match after the get_first_filename() call, */
  400. /* and returns 0 if a match was found, nonzero otherwise.  The name is in the */
  401. /* current dta */
  402.  
  403. static unsigned int get_next_filename(fnameptr)
  404. unsigned long int fnameptr;
  405. {
  406.     address_union address;  /* address conversion union */
  407.     union REGS inregs, outregs;
  408.     struct SREGS segregs;
  409.  
  410.  
  411.     /* get first filename */
  412.     address.pointer=fnameptr;
  413.     segregs.ds=address.s.segment;
  414.     inregs.x.dx=address.s.offset;
  415.     inregs.x.cx=0;  /* no funny attributes in file */
  416.     inregs.h.ah=0x4F;  /* set function number for continuing search */
  417.     intdosx(&inregs, &outregs, &segregs);
  418.  
  419.     return outregs.x.cflag;
  420.  
  421. }
  422.  
  423.  
  424.  
  425.  
  426.  
  427. /* set_dta() sets the address for the start of the new dta */
  428.  
  429. static void set_dta(pointer)
  430. unsigned long pointer;
  431. {
  432.     address_union address;
  433.     union REGS inregs, outregs;
  434.     struct SREGS segregs;
  435.  
  436.         /* set up the dta */
  437.     address.pointer=pointer;
  438.     segregs.ds=address.s.segment;
  439.     inregs.x.dx=address.s.offset;
  440.     inregs.h.ah=0x1A;   /* the function that tells DOS that POINTER is a dta */
  441.     intdosx(&inregs, &outregs, &segregs);
  442.  
  443. }
  444.  
  445.  
  446.  
  447.